/***************************************************************************
 *                                Serial.cs
 *                            -------------------
 *   begin                : May 1, 2002
 *   copyright            : (C) The RunUO Software Team
 *   email                : info@runuo.com
 *
 *   $Id: Serial.cs 4 2006-06-15 04:28:39Z mark $
 *
 ***************************************************************************/

/***************************************************************************
 *
 *   This program is free software; you can redistribute it and/or modify
 *   it under the terms of the GNU General Public License as published by
 *   the Free Software Foundation; either version 2 of the License, or
 *   (at your option) any later version.
 *
 ***************************************************************************/

using System;

namespace Server
{
	public struct Serial : IComparable, IComparable<Serial>
	{
		private int m_Serial;

		private static Serial m_LastMobile = Zero;
		private static Serial m_LastItem = 0x40000000;

		public static Serial LastMobile { get { return m_LastMobile; } }
		public static Serial LastItem { get { return m_LastItem; } }

		public static readonly Serial MinusOne = new Serial( -1 );
		public static readonly Serial Zero = new Serial( 0 );

		public static Serial NewMobile
		{
			get
			{
				while ( World.FindMobile( m_LastMobile = (m_LastMobile + 1) ) != null );

				return m_LastMobile;
			}
		}

		public static Serial NewItem
		{
			get
			{
				while ( World.FindItem( m_LastItem = (m_LastItem + 1) ) != null );

				return m_LastItem;
			}
		}

		private Serial( int serial )
		{
			m_Serial = serial;
		}

		public int Value
		{
			get
			{
				return m_Serial;
			}
		}

		public bool IsMobile
		{
			get
			{
				return ( m_Serial > 0 && m_Serial < 0x40000000 );
			}
		}

		public bool IsItem
		{
			get
			{
				return ( m_Serial >= 0x40000000 && m_Serial <= 0x7FFFFFFF );
			}
		}

		public bool IsValid
		{
			get
			{
				return ( m_Serial > 0 );
			}
		}

		public override int GetHashCode()
		{
			return m_Serial;
		}

		public int CompareTo( Serial other )
		{
			return m_Serial.CompareTo( other.m_Serial );
		}

		public int CompareTo( object other )
		{
			if ( other is Serial )
				return this.CompareTo( (Serial) other );
			else if ( other == null )
				return -1;

			throw new ArgumentException();
		}

		public override bool Equals( object o )
		{
			if ( o == null || !(o is Serial) ) return false;

			return ((Serial)o).m_Serial == m_Serial;
		}

		public static bool operator == ( Serial l, Serial r )
		{
			return l.m_Serial == r.m_Serial;
		}

		public static bool operator != ( Serial l, Serial r )
		{
			return l.m_Serial != r.m_Serial;
		}

		public static bool operator > ( Serial l, Serial r )
		{
			return l.m_Serial > r.m_Serial;
		}

		public static bool operator < ( Serial l, Serial r )
		{
			return l.m_Serial < r.m_Serial;
		}

		public static bool operator >= ( Serial l, Serial r )
		{
			return l.m_Serial >= r.m_Serial;
		}

		public static bool operator <= ( Serial l, Serial r )
		{
			return l.m_Serial <= r.m_Serial;
		}

		/*public static Serial operator ++ ( Serial l )
		{
			return new Serial( l + 1 );
		}*/

		public override string ToString()
		{
			return String.Format( "0x{0:X8}", m_Serial );
		}

		public static implicit operator int( Serial a )
		{
			return a.m_Serial;
		}

		public static implicit operator Serial( int a )
		{
			return new Serial( a );
		}
	}
}